package com.benchmark.springboot.controller;

import com.benchmark.springboot.enums.ErrorCodeEnum;
import com.benchmark.springboot.quartz.JobResult;
import com.benchmark.springboot.quartz.ScheduleJob;
import com.benchmark.springboot.quartz.factory.DynamicJobFactory;
import com.power.common.constants.BaseErrorCode;
import com.power.common.model.CommonResult;
import lombok.extern.slf4j.Slf4j;
import org.quartz.JobDataMap;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import javax.annotation.Resource;
import java.util.ArrayList;
import java.util.List;
import java.util.UUID;

/**
 * jvm各内存溢出测试
 */
@Slf4j
@RestController
@RequestMapping("memory")
public class MemoryOutController {

    private static final String DIRECT_OUT_JOB = "com.benchmark.springboot.job.DirectoryMemoryOutJob";

    private List<String> stringList = new ArrayList<>();

    @Resource
    private DynamicJobFactory dynamicJobFactory;

    /**
     * 堆内存溢出测试
     * @return
     */
    @GetMapping("heapOut")
    public CommonResult heap() {
        int i = 0;
        while (true) {
            stringList.add(UUID.randomUUID().toString());
            log.info("i=", i);
            i++;
        }
    }

    /**
     * 启动直接内存占用溢出任务
     * @apiNote 配置停顿时间方便观察
     * @param sleepTime 停顿时间|1000
     * @return
     */
    @GetMapping("directoryMemoryOut/{sleepTime}")
    public CommonResult directoryMemoryStart(@PathVariable long sleepTime) {
        ScheduleJob scheduleJob = new ScheduleJob();
        scheduleJob.setClassName(DIRECT_OUT_JOB);
        scheduleJob.setChineseName("直接内存溢出");
        scheduleJob.setUniqueKey(DIRECT_OUT_JOB + "_rest");
        JobDataMap jobDataMap = new JobDataMap();
        jobDataMap.put("sleepTime",sleepTime);
        try {
            JobResult jobResult = dynamicJobFactory.addNowRunJob(scheduleJob, jobDataMap);
            if (!jobResult.isSuccess()) {
                return CommonResult.fail(ErrorCodeEnum.JOB_ERROR.getCode(), jobResult.getMessage());
            }
        } catch (Exception e) {
            log.error("直接内存溢出任务报错", e);
            return CommonResult.fail(BaseErrorCode.Common.UNKNOWN_ERROR);
        }
        return CommonResult.ok();
    }

    /**
     * 停止直接内存占用溢出任务
     * @return
     */
    @GetMapping("directoryMemoryOutStop")
    public CommonResult directoryMemoryStop() {
        try {
            dynamicJobFactory.stop(DIRECT_OUT_JOB);
        } catch (Exception e) {
            log.error("停止直接内存溢出任务报错", e);
            return CommonResult.fail(BaseErrorCode.Common.UNKNOWN_ERROR);
        }
        return CommonResult.ok();
    }
}
